#include <functional>
#include <mutex>
#include <iostream>
#include <cstdint>

using namespace std;

#ifdef WIN32
#include <windows.h>
#else
typedef unsigned long DWORD;
#endif

template <typename T, typename... Args>
void x1(std::function<void(bool)> callback, const T &fn, Args &&...args)
{
}

template <typename T, typename... Args>
void x2(T &&fn, Args &&...args)
{
	auto call = std::bind(
		&x1<std::remove_reference_t<T>, std::remove_reference_t<Args>...>,
		std::placeholders::_1,
		std::forward<T>(fn),
		args...);
	call(std::function<void(bool)>{});
}

void callxxx(std::mutex &lock)
{
}

#define SIZEOF(t) "sizeof(" << #t << ") = [" << sizeof(t) << "]"

int main(int argc, char **argv)
{
	std::mutex lock;
	x2(&callxxx, std::ref(lock));

	cout << SIZEOF(int64_t) << endl;
	cout << SIZEOF(DWORD) << endl;
	cout << SIZEOF(uint32_t) << endl;

	return 0;
}
